package ModelGenerator;

import java.io.BufferedInputStream;
import java.io.BufferedReader;
import java.io.DataInputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.io.PrintStream;
import java.util.Date;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.Set;
import java.util.Map.Entry;
import java.util.zip.ZipEntry;
import java.util.zip.ZipInputStream;


public class FileReader {

	public static Records recordList = new Records();
	public static Records testList = new Records();
	public static TouchRecords trainTouchList = new TouchRecords();
	public static TouchRecords testTouchList = new TouchRecords();

	public static ArrayList<String> newProcesses = new ArrayList<String>();
	public static ArrayList<FinalRecords> posFinalRecords  = new ArrayList<FinalRecords>();
	public static ArrayList<FinalRecords> negFinalRecords  = new ArrayList<FinalRecords>();


	public static HashMap<String, int[]> trainProcesses = new HashMap<String, int[]>();
	public static HashMap<String, int[][]> trainProcessesPerDay = new HashMap<String, int[][]>();
	public static HashMap<String, int[]> testProcesses = new HashMap<String, int[]>();



	public static HashMap<String, String> trainChatGroup = new HashMap<String, String>();
	public static HashMap<String, String> testChatGroup = new HashMap<String, String>();


	public static HashMap<String, int[]> trainTouchProcesses = new HashMap<String, int[]>();
	public static HashMap<String, int[][]> trainTouchProcessesPerDay = new HashMap<String, int[][]>()	;
	//public static HashMap<String, int[]> trainTouchOnlyProcesses = new HashMap<String, int[]>();

	public static HashMap<String, int[]> testTouchProcesses = new HashMap<String, int[]>();
	//public static HashMap<String, int[][]> testTouchProcessesPerDay = new HashMap<String, int[][]>();
	//public static HashMap<String, int[]> testTouchOnlyProcesses = new HashMap<String, int[]>();

	public static int max=0,min=0,days=0;
	public static int max2=0,min2=0,days2=0;
	public static int max3=0,min3=0,days3=0;
	public static int max4=0,min4=0,days4=0;
	public static int max5=0,min5=0,days5=0;
	public static int max6=0,min6=0,days6=0;

	public static double threshold ;


	public static	PrintStream out;


	public static void main(String[] args){

		try {
			
			
			out	 = new PrintStream("output_"+args[2]+"_time_"+System.currentTimeMillis()+".txt");



			threshold = Double.parseDouble(args[2].toString());
			String traindata = args[0];
			String testdata = args[1];

			String touchLogsTrain = null;
			String testLogsTrain = null;

			if(args.length==5){
				touchLogsTrain = args[3];
				testLogsTrain = args[4];
			}

			File dir ;
			String[] children ;



			if(touchLogsTrain!=null && testLogsTrain!=null){

				dir = new File(touchLogsTrain);
				children = dir.list();

				for(String filename : children){
					System.out.println(touchLogsTrain + File.separatorChar + filename);
					readFileTouch(touchLogsTrain + File.separatorChar + filename);
					//putTrainTouchHashRecords();

					//	trainTouchList=new TouchRecords();
				}

				dir = new File(touchLogsTrain);
				children = dir.list();

				for(String filename : children){
					System.out.println(touchLogsTrain + File.separatorChar + filename);
					readFileTouch2(touchLogsTrain + File.separatorChar + filename);
					//	putTrainTouchHashRecordsPerDay();

					//trainTouchList=new TouchRecords();
				}


				dir = new File(testLogsTrain);
				children = dir.list();

				for(String filename : children){
					System.out.println(testLogsTrain + File.separatorChar + filename);
					readFileTouchTest(testLogsTrain + File.separatorChar + filename);
					//putTestTouchHashRecords();

					//testTouchList=new TouchRecords();
				}






				printHashTouchMap(trainTouchProcesses);
				System.out.println("Acquired in Days : "+days3);
				System.out.println();
				out.println("Acquired in Days : "+days3);
				out.println();

				//printHashTouchMap(trainTouchOnlyProcesses);
				//System.out.println("Acquired in Days : "+days4);
				//System.out.println();

				printHashTouchMapPerDay(trainTouchProcessesPerDay);
				System.out.println();
				out.println();


				printHashTouchMap(testTouchProcesses);
				System.out.println("Acquired in Days : "+days5);
				System.out.println();

				out.println("Acquired in Days : "+days5);
				out.println();




				//printHashTouchMapPerDay(testTouchProcessesPerDay);
				compareFileTouched();
				System.out.println();
				out.println();

			}
			else{
				System.out.println("-----------NO Touch Logs");
				out.println("-----------NO Touch Logs");


			}





			dir = new File(traindata);
			children = dir.list();

			for(String filename : children){
				System.out.println(traindata + File.separatorChar + filename);
				readFile(traindata + File.separatorChar + filename);
				//	putHashRecords();

				//			recordList=new Records();
			}

			dir = new File(traindata);
			children = dir.list();

			for(String filename : children){
				System.out.println(traindata + File.separatorChar + filename);
				readFile2(traindata + File.separatorChar + filename);
				//putHashRecordsPerDay();

				//recordList=new Records();
			}





			dir = new File(testdata);
			String[] children2 = dir.list();

			for(String filename : children2){
				System.out.println(testdata + File.separatorChar + filename);
				readTestFile(testdata + File.separatorChar + filename);
				//putTestHashRecords();

				//testList=new Records();


			}


			printHashMap(trainProcesses);
			System.out.println("Acquired in Days : "+days);
			System.out.println();

			out.println("Acquired in Days : "+days);
			out.println();


			printHashTouchMapPerDay(trainProcessesPerDay);
			System.out.println();
			out.println();


			printHashMap(testProcesses);
			System.out.println("Acquired in Days : "+days2);
			System.out.println();

			out.println("Acquired in Days : "+days2);
			out.println();

			compareChatGroup();
			System.out.println();
			out.println();



			compareMaps();

			printResults();

			out.close();
		}
		catch (IOException e) {
			e.printStackTrace();
		}
	}



	private static void printResults() {
		// TODO Auto-generated method stub
		int count=0;
		System.out.println("New Proceeses/Applications used -");
		out.println("New Proceeses/Applications used -");
		for(String pro: newProcesses)
		{
			count++;
			System.out.println(count+ ". " +pro);
			out.println(count+ ". " +pro);
		}

		printFinalRecords(posFinalRecords, "Postive");
		printFinalRecords(negFinalRecords, "Negative");




	}



	private static void printFinalRecords(ArrayList<FinalRecords> rrecords, String caseType) {
		// TODO Auto-generated method stub

		System.out.println();
		System.out.println(caseType + " Alerts ---");
		out.println();
		out.println(caseType + " Alerts ---");

		for(FinalRecords r : rrecords){

			System.out.println(r.count + ". "+ r.process +" at "+r.time+" hr "+ " -- "+r.avgtest+" " + r.avgtrain +" "+r.sd+" "+r.gaussresult );
			out.println(r.count + ". "+ r.process +" at "+r.time+"hr "+ " -- "+r.avgtest+" " + r.avgtrain +" "+r.sd+" "+r.gaussresult );



		}

		System.out.println();
		out.println();
	}



	private static void putHashRecordsPerDay() {

		int count = 0;
		for(Record r : recordList.records){
			count++;


			if(trainProcessesPerDay.containsKey(r.processExecutablename)){

				int countt[][] = trainProcessesPerDay.get(r.processExecutablename);
				if(countt==null){
					System.out.println("hit");
				}else{
					int time=getTimeFirst(r.plainTextDateTime);
					int dayy=getDayFirst(r.plainTextDateTime);

					if(time != -1 ){
						//	System.out.println(time +" "+ countt.length );
						countt[dayy-min][time]=countt[dayy-min][time]+1;
					}
					trainProcessesPerDay.remove(r.processExecutablename);
					trainProcessesPerDay.put(r.processExecutablename, countt);
				}
			}
			else{
				int perHour[][]= new int[days][24];
				int time=getTimeFirst(r.plainTextDateTime);
				int dayy=getDayFirst(r.plainTextDateTime);

				if(time != -1){
					perHour[dayy-min][time]=1;
					trainProcessesPerDay.put(r.processExecutablename, perHour);
				}
			}

		}


	}



	@SuppressWarnings("deprecation")
	private static int getDayFirst(String plainTextDateTime) {

		DateFormat df = new SimpleDateFormat("MM/dd/yyyy h:m:s a");
		//System.out.println(plainTextDateTime );
		try{

			Date today = df.parse(plainTextDateTime);            

			//int day=today.getDate();

			//System.out.println("Today = " + df.format(today));
			//System.out.println("Today = " + today.getHours());
			return today.getDate();
		} catch (Exception e)

		{
			//e.printStackTrace();
			return -1;

		}

	}


	@SuppressWarnings("deprecation")
	private static int getTimeFirst(String plainTextDateTime) {
		DateFormat df = new SimpleDateFormat("MM/dd/yyyy h:m:s a");
		//System.out.println(plainTextDateTime );
		try{

			Date today = df.parse(plainTextDateTime);            

			//int day=today.getDate();

			//System.out.println("Today = " + df.format(today));
			//System.out.println("Today = " + today.getHours());
			return today.getHours();
		} catch (Exception e)

		{
			//e.printStackTrace();
			return -1;

		}
	}


	private static void printHashTouchMapPerDay(HashMap<String, int[][]> trainTouchProcessesPerDay2) {

		Set myOwnIterator = trainTouchProcessesPerDay2.entrySet();
		int count=0;
		Iterator myVeryOwnIterator = myOwnIterator.iterator();

		while(myVeryOwnIterator.hasNext()) {
			count++;
			Map.Entry m= (Entry) myVeryOwnIterator.next();
			String pro = (String)m.getKey();
			System.out.print(count +" "+pro+" ");
			out.print(count +" "+pro+" ");
			int timehrs[][] =(int [][]) m.getValue();
			for (int k =0; k<timehrs.length;k++){
				for (int j =0; j<24;j++){
					if(timehrs[k][j]!=0){
						System.out.print("---Day " +(k+1)+" Hr "+ j +" Count "+timehrs[k][j]+ ", ");
						out.print("---Day " +(k+1)+" Hr "+ j +" Count "+timehrs[k][j]+ ", ");

					}
				}
			}
			System.out.println();
			out.println();
		}

	}


	private static void putTestTouchHashRecords() {

		int count = 0;
		for(TouchRecord r : testTouchList.touchRecords){
			count++;

			if(testTouchProcesses.containsKey(r.processExecutablename)){

				int countt[] = testTouchProcesses.get(r.processExecutablename);
				if(countt==null){
					System.out.println("hit");
				}else{
					int time=checkTimeTouchTest(r.time);
					if(time != -1 ){
						//	System.out.println(time +" "+ countt.length );
						countt[time]=countt[time]+1;
					}
					testTouchProcesses.remove(r.processExecutablename);
					testTouchProcesses.put(r.processExecutablename, countt);
				}
			}
			else{
				int perHour[]= new int[24];
				int time=checkTimeTouchTest(r.time);
				if(time != -1){
					perHour[time]=1;
					testTouchProcesses.put(r.processExecutablename, perHour);
				}
			}

		}

	}


	@SuppressWarnings("deprecation")
	private static int checkTimeTouchTrainOnly(String time) {


		DateFormat df = new SimpleDateFormat("h:m:s a MM/dd/yyyy");
		//System.out.println(plainTextDateTime );
		try{

			Date today = df.parse(time);            

			int day=today.getDate();
			if(min6==0){
				min6=day;
			}

			if(day>max6){
				max6=day;
			}

			if(max6==min6){
				days6=1;
			}
			else{
				days6=(max6-min6)+1;
			}
			//System.out.println("Today = " + df.format(today));
			//System.out.println("Today = " + today.getHours());
			return today.getHours();
		} catch (Exception e)

		{
			//e.printStackTrace();
			return -1;

		}

	}


	@SuppressWarnings("deprecation")
	private static int checkTimeTouchTest(String time) {
		DateFormat df = new SimpleDateFormat("h:m:s a MM/dd/yyyy");
		//System.out.println(plainTextDateTime );
		try{

			Date today = df.parse(time);            

			int day=today.getDate();
			if(min5==0){
				min5=day;
			}

			if(day>max5){
				max5=day;
			}

			if(max5==min5){
				days5=1;
			}
			else{
				days5=(max5-min5)+1;
			}
			//System.out.println("Today = " + df.format(today));
			//System.out.println("Today = " + today.getHours());
			return today.getHours();
		} catch (Exception e)

		{
			//e.printStackTrace();
			return -1;

		}

	}



	private static void readFileTouchTest(String filename) {

		try{
			// Open the file that is the first 
			// command line parameter
			FileInputStream fstream = new FileInputStream(filename);
			// Get the object of DataInputStream
			DataInputStream in = new DataInputStream(fstream);
			BufferedReader br = new BufferedReader(new InputStreamReader(in));
			String strLine;
			//Read File Line By Line

			while ((strLine = br.readLine()) != null)   {
				// Print the content on the console
				//StringTokenizer str = strLine.
				String[] group = strLine.split(" ");

				TouchRecord r = new TouchRecord(group);

				if(testTouchProcesses.containsKey(r.processExecutablename)){

					int countt[] = testTouchProcesses.get(r.processExecutablename);
					if(countt==null){
						System.out.println("hit");
					}else{
						int time=checkTimeTouchTest(r.time);
						if(time != -1 ){
							//	System.out.println(time +" "+ countt.length );
							countt[time]=countt[time]+1;
						}
						testTouchProcesses.remove(r.processExecutablename);
						testTouchProcesses.put(r.processExecutablename, countt);
					}
				}
				else{
					int perHour[]= new int[24];
					int time=checkTimeTouchTest(r.time);
					if(time != -1){
						perHour[time]=1;
						testTouchProcesses.put(r.processExecutablename, perHour);
					}
				}

				//	testTouchList.touchRecords.add(new TouchRecord(group));

			}
			//Close the input stream
			in.close();
		}catch (Exception e){//Catch exception if any
			System.err.println("Error: " + e.getMessage());
		}

	}


	private static void printHashTouchMap(HashMap<String, int[]> recordListPrint) {

		Set myOwnIterator = recordListPrint.entrySet();
		int count=0;
		Iterator myVeryOwnIterator = myOwnIterator.iterator();

		while(myVeryOwnIterator.hasNext()) {
			count++;
			Map.Entry m= (Entry) myVeryOwnIterator.next();
			String pro = (String)m.getKey();
			System.out.print(count +" "+pro+" ");
			out.print(count +" "+pro+" ");
			int timehrs[] =(int []) m.getValue();
			for (int k =0; k<timehrs.length;k++){
				if(timehrs[k]!=0){
					System.out.print(" " +(k)+" "+timehrs[k]);
					out.print(" " +(k)+" "+timehrs[k]);

				}
			}
			System.out.println();
			out.println();
		}
	}

	private static void putTrainTouchHashRecords() {


		int count = 0;
		for(TouchRecord r : trainTouchList.touchRecords){
			count++;



			if(trainTouchProcesses.containsKey(r.processExecutablename)){

				int countt[] = trainTouchProcesses.get(r.processExecutablename);
				if(countt==null){
					System.out.println("hit");
				}else{
					int time=checkPatternTimeTouch(r.time);
					if(time != -1 ){
						//	System.out.println(time +" "+ countt.length );
						countt[time]=countt[time]+1;
					}
					trainTouchProcesses.remove(r.processExecutablename);
					trainTouchProcesses.put(r.processExecutablename, countt);
				}
			}
			else{
				int perHour[]= new int[24];
				int time=checkPatternTimeTouch(r.time);
				if(time != -1){
					perHour[time]=1;
					trainTouchProcesses.put(r.processExecutablename, perHour);
				}
			}

		}

	}


	@SuppressWarnings("deprecation")
	private static int checkPatternTimeTouchOnly(String plainTextDateTime) {
		DateFormat df = new SimpleDateFormat("h:m:s a MM/dd/yyyy");
		//System.out.println(plainTextDateTime );
		try{

			Date today = df.parse(plainTextDateTime);            

			int day=today.getDate();
			if(min4==0){
				min4=day;
			}

			if(day>max4){
				max4=day;
			}

			if(max4==min4){
				days4=1;
			}
			else{
				days4=(max4-min4)+1;
			}
			//System.out.println("Today = " + df.format(today));
			//System.out.println("Today = " + today.getHours());
			return today.getHours();
		} catch (Exception e)

		{
			//e.printStackTrace();
			return -1;

		}
	}


	@SuppressWarnings("deprecation")
	private static int checkPatternTimeTouch(String plainTextDateTime) {
		DateFormat df = new SimpleDateFormat("h:m:s a MM/dd/yyyy");
		//System.out.println(plainTextDateTime );
		try{

			Date today = df.parse(plainTextDateTime);            

			int day=today.getDate();
			if(min3==0){
				min3=day;
			}

			if(day>max3){
				max3=day;
			}

			if(max3==min3){
				days3=1;
			}
			else{
				days3=(max3-min3)+1;
			}
			//System.out.println("Today = " + df.format(today));
			//System.out.println("Today = " + today.getHours());
			return today.getHours();
		} catch (Exception e)

		{
			//e.printStackTrace();
			return -1;

		}
	}


	private static void readFileTouch2(String filename) {
		try{
			// Open the file that is the first 
			// command line parameter
			FileInputStream fstream = new FileInputStream(filename);
			// Get the object of DataInputStream
			DataInputStream in = new DataInputStream(fstream);
			BufferedReader br = new BufferedReader(new InputStreamReader(in));
			String strLine;
			//Read File Line By Line

			while ((strLine = br.readLine()) != null)   {
				// Print the content on the console
				//StringTokenizer str = strLine.
				String[] group=strLine.split(" ");


				TouchRecord r = new TouchRecord(group);


				if(trainTouchProcessesPerDay.containsKey(r.processExecutablename)){

					int countt[][] = trainTouchProcessesPerDay.get(r.processExecutablename);
					if(countt==null){
						System.out.println("hit");
					}else{
						int time=getTimee(r.time);
						int dayy =getDayy(r.time);


						if(time != -1 ){
							//	System.out.println(time +" "+ countt.length );
							countt[dayy-min3][time]=countt[dayy-min3][time]+1;
						}
						trainTouchProcessesPerDay.remove(r.processExecutablename);
						trainTouchProcessesPerDay.put(r.processExecutablename, countt);
					}
				}
				else{
					int perHour[][]= new int[days3][24];
					int time=getTimee(r.time);
					int dayy =getDayy(r.time);

					if(time != -1){
						perHour[dayy-min3][time]=1;
						trainTouchProcessesPerDay.put(r.processExecutablename, perHour);
					}
				}


			}
			//Close the input stream
			in.close();
		}catch (Exception e){//Catch exception if any
			System.err.println("Error: " + e.getMessage());
		}

	}


	private static void readFileTouch(String filename) {
		try{
			// Open the file that is the first 
			// command line parameter
			FileInputStream fstream = new FileInputStream(filename);
			// Get the object of DataInputStream
			DataInputStream in = new DataInputStream(fstream);
			BufferedReader br = new BufferedReader(new InputStreamReader(in));
			String strLine;
			//Read File Line By Line

			while ((strLine = br.readLine()) != null)   {
				// Print the content on the console
				//StringTokenizer str = strLine.
				String[] group=strLine.split(" ");


				TouchRecord r = new TouchRecord(group);


				if(trainTouchProcesses.containsKey(r.processExecutablename)){

					int countt[] = trainTouchProcesses.get(r.processExecutablename);
					if(countt==null){
						System.out.println("hit");
					}else{
						int time=checkPatternTimeTouch(r.time);
						if(time != -1 ){
							//	System.out.println(time +" "+ countt.length );
							countt[time]=countt[time]+1;
						}
						trainTouchProcesses.remove(r.processExecutablename);
						trainTouchProcesses.put(r.processExecutablename, countt);
					}
				}
				else{
					int perHour[]= new int[24];
					int time=checkPatternTimeTouch(r.time);
					if(time != -1){
						perHour[time]=1;
						trainTouchProcesses.put(r.processExecutablename, perHour);
					}
				}

			}
			//Close the input stream
			in.close();
		}catch (Exception e){//Catch exception if any
			System.err.println("Error: " + e.getMessage());
		}

	}



	private static void printChatGroup(HashMap<String, String> testChatGroup2) {


		Set myOwnIterator = testChatGroup2.entrySet();
		int count=0;
		Iterator myVeryOwnIterator = myOwnIterator.iterator();

		while(myVeryOwnIterator.hasNext()) {
			count++;
			Map.Entry m= (Entry) myVeryOwnIterator.next();
			String pro = (String)m.getKey();
			String pro2 = (String)m.getValue();

			System.out.print(count +" "+pro+" " + pro2);

			System.out.println();
		}

	}



	private static void compareChatGroup() {
		System.out.println();
		System.out.println("Possible New Users Found in the chat group -- ");

		out.println();
		out.println("Possible New Users Found in the chat group -- ");

		Set myOwnIterator = testChatGroup.entrySet();
		int count=0;

		Iterator myVeryOwnIterator = myOwnIterator.iterator();

		while(myVeryOwnIterator.hasNext()) {

			Map.Entry m= (Entry) myVeryOwnIterator.next();
			String pro = (String) m.getKey();

			if(!(trainChatGroup.containsKey(pro))){
				count++;
				System.out.println(count+" --New User Anomaly -- "+pro);
				out.println(count+" ---- "+pro);
			}
		}

		System.out.println();
		out.println();

	}



	private static void compareFileTouched() {
		// TODO Auto-generated method stub

		Set myOwnIterator = testTouchProcesses.entrySet();
		int count=0;

		double avgtrain, avgtest;

		Iterator myVeryOwnIterator = myOwnIterator.iterator();

		while(myVeryOwnIterator.hasNext()) {

			Map.Entry m= (Entry) myVeryOwnIterator.next();
			String pro = (String) m.getKey();

			if(trainTouchProcesses.containsKey(pro)){

				int trainTime[]=trainTouchProcesses.get(pro);
				int testTime[] =(int []) m.getValue();

				for (int k =0; k<testTime.length;k++){

					if(testTime[k]!= 0){

						avgtrain = (double)((double)trainTime[k]/(double)days3);
						avgtest = (double)((double)testTime[k]/(double)days5);
						//need to add some strong logic here
						int trainTimeTouch[][]=trainTouchProcessesPerDay.get(pro);
						double sd=0;
						for(int ll=0;ll<trainTimeTouch.length;ll++){
							//System.out.print(k+ " "+ ll + " "+trainTimeTouch[ll][k]+"  ");
							sd+=((trainTimeTouch[ll][k]-avgtrain)*(trainTimeTouch[ll][k]-avgtrain));
						}
						double mid =sd;
						sd=(double)((double)sd/(double)(trainTimeTouch.length));


						sd = (double) Math.sqrt(sd);

						double gaussresult = getGaussianScore(sd, avgtrain, avgtest);


						//	if(avgtest > (2 * avgtrain)){
						if(gaussresult < threshold){
							count++;
							System.out.println(" ------"+count+ "----New Gaussian File Touch Anomaly -- "+pro+ " time "  +(k)+ " " + avgtest + " " + (avgtrain) +" sd "+sd+ " "+ mid+ " "+ gaussresult);
							out.println(" ------"+count+ "----New Gaussian File Touch Anomaly -- "+pro+ " time "  +(k)+ " " + avgtest + " " + (avgtrain) +" sd "+sd+ " "+ mid+ " "+ gaussresult);


						}

					}

				}

			}
			else{
				System.out.println(" New Process Anomaly -- "+pro);
				out.println(" New Process Anomaly -- "+pro);
			}

		}

	}


	private static double getGaussianScore(double sd, double avgtrain,	double avgtest) {
		if(sd != 0){
			double first = (double) (1/(Math.sqrt((double)2*3.14*sd*sd)));
			double mid =-(double)(((avgtest-avgtrain)*(avgtest-avgtrain))/((double)2*sd*sd));
			double result =(double) (first * Math.exp(mid));
			return result;
		}
		else return 0;

	}


	private static void compareMaps() {
		// TODO Auto-generated method stub

		Set myOwnIterator = testProcesses.entrySet();
		int count=0,count2=0;

		double avgtrain, avgtest;

		Iterator myVeryOwnIterator = myOwnIterator.iterator();

		while(myVeryOwnIterator.hasNext()) {

			Map.Entry m= (Entry) myVeryOwnIterator.next();
			String pro = (String) m.getKey();

			if(trainProcesses.containsKey(pro)){

				int trainTime[]=trainProcesses.get(pro);
				int testTime[] =(int []) m.getValue();

				for (int k =0; k<testTime.length;k++){

					if(testTime[k]!= 0){

						avgtrain = (double)((double)trainTime[k]/(double)days);
						avgtest = (double)((double)testTime[k]/(double)days2);
						//need to add some strong logic here


						int trainTimeTouch[][]=trainProcessesPerDay.get(pro);
						double sd=0;
						for(int ll=0;ll<trainTimeTouch.length;ll++){
							//System.out.print(k+ " "+ ll + " "+trainTimeTouch[ll][k]+"  ");
							sd+=((trainTimeTouch[ll][k]-avgtrain)*(trainTimeTouch[ll][k]-avgtrain));
						}
						double mid =sd;
						sd=(double)((double)sd/(double)(trainTimeTouch.length));


						sd = (double) Math.sqrt(sd);

						double gaussresult = getGaussianScore(sd, avgtrain, avgtest);


						//if(avgtest > (2 * avgtrain)){
						if(gaussresult < threshold){	
							count++;
							//System.out.println(count+ "Pos----New Rate/Hour Anomaly -- "+pro+ " "  +(k)+ " " + avgtest + " avgtrain " + (avgtrain)+ " sd "+sd+ " "+mid+" "+gaussresult);

							//	out.println(count+ "Pos----New Rate/Hour Anomaly -- "+pro+ " "  +(k)+ " " + avgtest + " avgtrain " + (avgtrain)+ " sd "+sd+ " "+mid+" "+gaussresult);

							posFinalRecords.add(new FinalRecords(count, pro, k, avgtest,avgtrain,sd,gaussresult));

						}
						else{
							count2++;
							//System.out.println(count2+ "Neg----New Rate/Hour Normal -- "+pro+ " "  +(k)+ " " + avgtest + " avgtrain " + (avgtrain)+ " sd "+sd+" "+gaussresult);

							//out.println(count2+ "Neg----New Rate/Hour Normal -- "+pro+ " "  +(k)+ " " + avgtest + " avgtrain " + (avgtrain)+ " sd "+sd+" "+gaussresult);
							negFinalRecords.add(new FinalRecords(count2, pro, k, avgtest,avgtrain,sd,gaussresult));
						}

					}

				}

			}
			else{
				//count++;
				if(!(newProcesses.contains(pro))){
					newProcesses.add(pro);
				}

			}

		}

	}



	private static void printHashMap(HashMap<String, int[]> recordListPrint) {

		Set myOwnIterator = recordListPrint.entrySet();
		int count=0;
		Iterator myVeryOwnIterator = myOwnIterator.iterator();

		while(myVeryOwnIterator.hasNext()) {
			count++;
			Map.Entry m= (Entry) myVeryOwnIterator.next();
			String pro = (String)m.getKey();
			System.out.print(count +" "+pro+" ");
			out.print(count +" "+pro+" ");
			int timehrs[] =(int []) m.getValue();
			for (int k =0; k<timehrs.length;k++){
				if(timehrs[k]!=0){
					System.out.print(" " +(k)+" "+timehrs[k]);
					out.print(" " +(k)+" "+timehrs[k]);

				}
			}
			System.out.println();
			out.println();
		}

	}




	private static void putHashRecords() {
		int count = 0;
		for(Record r : recordList.records){
			count++;

			if((r.processExecutablename.toLowerCase().equals("googletalk.exe") || r.processExecutablename.toLowerCase().equals("skype.exe") || r.processExecutablename.toLowerCase().equals("yahoomessenger.exe")) && ((r.typeOfAuditAction.equals("USERTOUCH_1"))||(r.typeOfAuditAction.equals("TITLETOUCH_0")))  ){
				if(!(trainChatGroup.containsKey(r.titleOfWindowTouched))){
					trainChatGroup.put(r.titleOfWindowTouched, r.typeOfAuditAction);
				}
				else{
					String val =trainChatGroup.get(r.titleOfWindowTouched);
					val=val+" "+r.typeOfAuditAction;
					trainChatGroup.remove(r.titleOfWindowTouched);
					trainChatGroup.put(r.titleOfWindowTouched, val);
				}
			}

			if(trainProcesses.containsKey(r.processExecutablename)){

				int countt[] = trainProcesses.get(r.processExecutablename);
				if(countt==null){
					System.out.println("hit");
				}else{
					int time=checkPattern(r.plainTextDateTime);
					if(time != -1 ){
						//	System.out.println(time +" "+ countt.length );
						countt[time]=countt[time]+1;
					}
					trainProcesses.remove(r.processExecutablename);
					trainProcesses.put(r.processExecutablename, countt);
				}
			}
			else{
				int perHour[]= new int[24];
				int time=checkPattern(r.plainTextDateTime);
				if(time != -1){
					perHour[time]=1;
					trainProcesses.put(r.processExecutablename, perHour);
				}
			}

		}

	}

	private static void putTestHashRecords() {

		int count = 0;
		for(Record r : testList.records){
			count++;

			if(r.processExecutablename.toLowerCase().equals("googletalk.exe") && ((r.typeOfAuditAction.equals("USERTOUCH_1"))||(r.typeOfAuditAction.equals("TITLETOUCH_0")))){
				if(!(testChatGroup.containsKey(r.titleOfWindowTouched))){
					testChatGroup.put(r.titleOfWindowTouched, r.typeOfAuditAction);
				}
				else{
					String val =testChatGroup.get(r.titleOfWindowTouched);
					val=val+" "+r.typeOfAuditAction;
					testChatGroup.remove(r.titleOfWindowTouched);
					testChatGroup.put(r.titleOfWindowTouched, val);
				}
			}

			if(testProcesses.containsKey(r.processExecutablename)){

				int countt[] = testProcesses.get(r.processExecutablename);
				if(countt==null){
					System.out.println("hit");
				}else{
					int time=checkPatternTest(r.plainTextDateTime);
					if(time != -1 ){
						//	System.out.println(time +" "+ countt.length );
						countt[time]=countt[time]+1;
					}
					testProcesses.remove(r.processExecutablename);
					testProcesses.put(r.processExecutablename, countt);
				}
			}
			else{
				int perHour[]= new int[24];
				int time=checkPatternTest(r.plainTextDateTime);
				if(time != -1){
					perHour[time]=1;
					testProcesses.put(r.processExecutablename, perHour);
				}
			}

		}

	}


	@SuppressWarnings("deprecation")
	private static int checkPatternTest(String plainTextDateTime) {
		DateFormat df = new SimpleDateFormat("MM/dd/yyyy h:m:s a");
		//System.out.println(plainTextDateTime );
		try{

			Date today = df.parse(plainTextDateTime);            

			int day=today.getDate();
			if(min2==0){
				min2=day;
			}

			if(day>max2){
				max2=day;
			}

			if(max2==min2){
				days2=1;
			}
			else{
				days2=(max2-min2)+1;
			}
			//System.out.println("Today = " + df.format(today));
			//System.out.println("Today = " + today.getHours());
			return today.getHours();
		} catch (Exception e)

		{
			//e.printStackTrace();
			return -1;

		}

	}



	@SuppressWarnings("deprecation")
	private static int checkPattern(String plainTextDateTime) {
		DateFormat df = new SimpleDateFormat("MM/dd/yyyy h:m:s a");
		//System.out.println(plainTextDateTime );
		try{

			Date today = df.parse(plainTextDateTime);            

			int day=today.getDate();
			if(min==0){
				min=day;
			}

			if(day>max){
				max=day;
			}

			if(max==min){
				days=1;
			}
			else{
				days=(max-min)+1;
			}
			//System.out.println("Today = " + df.format(today));
			//System.out.println("Today = " + today.getHours());
			return today.getHours();
		} catch (Exception e)

		{
			//e.printStackTrace();
			return -1;

		}

	}


	private static void readFile2(String filename) {

		try{
			// Open the file that is the first 
			// command line parameter
			FileInputStream fstream = new FileInputStream(filename);
			// Get the object of DataInputStream
			DataInputStream in = new DataInputStream(fstream);
			BufferedReader br = new BufferedReader(new InputStreamReader(in));
			String strLine;
			//Read File Line By Line
			Record r=null;
			while ((strLine = br.readLine()) != null)   {
				// Print the content on the console

				String[] group=strLine.split("\t");
				if(group.length==10)
				{

					r =new Record(group);

					//	recordList.records.add(new Record(group));
					if(trainProcessesPerDay.containsKey(r.processExecutablename)){

						int countt[][] = trainProcessesPerDay.get(r.processExecutablename);
						if(countt==null){
							System.out.println("hit");
						}else{
							int time=getTimeFirst(r.plainTextDateTime);
							int dayy=getDayFirst(r.plainTextDateTime);

							if(time != -1 ){
								//	System.out.println(time +" "+ countt.length );
								countt[dayy-min][time]=countt[dayy-min][time]+1;
							}
							trainProcessesPerDay.remove(r.processExecutablename);
							trainProcessesPerDay.put(r.processExecutablename, countt);
						}
					}
					else{
						int perHour[][]= new int[days][24];
						int time=getTimeFirst(r.plainTextDateTime);
						int dayy=getDayFirst(r.plainTextDateTime);

						if(time != -1){
							perHour[dayy-min][time]=1;
							trainProcessesPerDay.put(r.processExecutablename, perHour);
						}
					}

				}

			}
			//Close the input stream
			in.close();
		}catch (Exception e){//Catch exception if any
			System.err.println("Error: " + e.getMessage());
		}
	}





	private static void readFile(String filename) {

		try{
			// Open the file that is the first 
			// command line parameter
			FileInputStream fstream = new FileInputStream(filename);
			// Get the object of DataInputStream
			DataInputStream in = new DataInputStream(fstream);
			BufferedReader br = new BufferedReader(new InputStreamReader(in));
			String strLine;
			//Read File Line By Line
			Record r=null;
			while ((strLine = br.readLine()) != null)   {
				// Print the content on the console

				String[] group=strLine.split("\t");
				if(group.length==10)
				{

					r = new Record(group);

					//	recordList.records.add(new Record(group));

					if((r.processExecutablename.toLowerCase().equals("googletalk.exe") || r.processExecutablename.toLowerCase().equals("skype.exe") || r.processExecutablename.toLowerCase().equals("yahoomessenger.exe")) && ((r.typeOfAuditAction.equals("USERTOUCH_1"))||(r.typeOfAuditAction.equals("TITLETOUCH_0")))  ){
						if(!(trainChatGroup.containsKey(r.titleOfWindowTouched))){
							String nam[]= r.titleOfWindowTouched.split(" ");
							if(nam.length<=1)
								trainChatGroup.put(r.titleOfWindowTouched, r.typeOfAuditAction);
						}
						else{
							String val =trainChatGroup.get(r.titleOfWindowTouched);
							val=val+" "+r.typeOfAuditAction;
							trainChatGroup.remove(r.titleOfWindowTouched);
							trainChatGroup.put(r.titleOfWindowTouched, val);
						}
					}

					if(trainProcesses.containsKey(r.processExecutablename)){

						int countt[] = trainProcesses.get(r.processExecutablename);
						if(countt==null){
							System.out.println("hit");
						}else{
							int time=checkPattern(r.plainTextDateTime);
							if(time != -1 ){
								//	System.out.println(time +" "+ countt.length );
								countt[time]=countt[time]+1;
							}
							trainProcesses.remove(r.processExecutablename);
							trainProcesses.put(r.processExecutablename, countt);
						}
					}
					else{
						int perHour[]= new int[24];
						int time=checkPattern(r.plainTextDateTime);
						if(time != -1){
							perHour[time]=1;
							trainProcesses.put(r.processExecutablename, perHour);
						}
					}

				}

			}
			//Close the input stream
			in.close();
		}catch (Exception e){//Catch exception if any
			System.err.println("Error: " + e.getMessage());
		}
	}




	private static void readTestFile(String filename) {

		try{
			// Open the file that is the first 
			// command line parameter
			FileInputStream fstream = new FileInputStream(filename);
			// Get the object of DataInputStream
			DataInputStream in = new DataInputStream(fstream);
			BufferedReader br = new BufferedReader(new InputStreamReader(in));
			String strLine;
			//Read File Line By Line

			while ((strLine = br.readLine()) != null)   {
				// Print the content on the console

				String[] group=strLine.split("\t");
				if(group.length==10)
				{


					Record r = new Record(group);



					if(r.processExecutablename.toLowerCase().equals("googletalk.exe") && ((r.typeOfAuditAction.equals("USERTOUCH_1"))||(r.typeOfAuditAction.equals("TITLETOUCH_0")))){
						if(!(testChatGroup.containsKey(r.titleOfWindowTouched))){
							String nam[]= r.titleOfWindowTouched.split(" ");
							if(nam.length<=1)
								testChatGroup.put(r.titleOfWindowTouched, r.typeOfAuditAction);
						}
						else{
							String val =testChatGroup.get(r.titleOfWindowTouched);
							val=val+" "+r.typeOfAuditAction;
							testChatGroup.remove(r.titleOfWindowTouched);
							testChatGroup.put(r.titleOfWindowTouched, val);
						}
					}

					if(testProcesses.containsKey(r.processExecutablename)){

						int countt[] = testProcesses.get(r.processExecutablename);
						if(countt==null){
							System.out.println("hit");
						}else{
							int time=checkPatternTest(r.plainTextDateTime);
							if(time != -1 ){
								//	System.out.println(time +" "+ countt.length );
								countt[time]=countt[time]+1;
							}
							testProcesses.remove(r.processExecutablename);
							testProcesses.put(r.processExecutablename, countt);
						}
					}
					else{
						int perHour[]= new int[24];
						int time=checkPatternTest(r.plainTextDateTime);
						if(time != -1){
							perHour[time]=1;
							testProcesses.put(r.processExecutablename, perHour);
						}
					}
					//System.out.println(count + " " + r.plainTextDateTime);
					//	checkPattern(r.plainTextDateTime);
					//System.out.println(count + " " + r.processExecutablename + " " + r.timestamp +" " + r.plainTextDateTime);



					//testList.records.add(new Record(group));

				}

			}
			//Close the input stream
			in.close();
		}catch (Exception e){//Catch exception if any
			System.err.println("Error: " + e.getMessage());
		}
	}




	private static void putTrainTouchHashRecordsPerDay() {

		int count = 0;
		for(TouchRecord r : trainTouchList.touchRecords){
			count++;

			if(trainTouchProcessesPerDay.containsKey(r.processExecutablename)){

				int countt[][] = trainTouchProcessesPerDay.get(r.processExecutablename);
				if(countt==null){
					System.out.println("hit");
				}else{
					int time=getTimee(r.time);
					int dayy =getDayy(r.time);


					if(time != -1 ){
						//	System.out.println(time +" "+ countt.length );
						countt[dayy-min3][time]=countt[dayy-min3][time]+1;
					}
					trainTouchProcessesPerDay.remove(r.processExecutablename);
					trainTouchProcessesPerDay.put(r.processExecutablename, countt);
				}
			}
			else{
				int perHour[][]= new int[days3][24];
				int time=getTimee(r.time);
				int dayy =getDayy(r.time);

				if(time != -1){
					perHour[dayy-min3][time]=1;
					trainTouchProcessesPerDay.put(r.processExecutablename, perHour);
				}
			}

		}

	}


	/*private static void putTestTouchHashRecordsPerDay() {

		int count = 0;
		for(TouchRecord r : testTouchList.touchRecords){
			count++;

			if(testTouchProcessesPerDay.containsKey(r.processExecutablename)){

				int countt[][] = testTouchProcessesPerDay.get(r.processExecutablename);
				if(countt==null){
					System.out.println("hit");
				}else{
					int time=getTimee(r.time);
					int dayy =getDayy(r.time);


					if(time != -1 ){
						//	System.out.println(time +" "+ countt.length );
						countt[dayy-min5][time]=countt[dayy-min5][time]+1;
					}
					testTouchProcessesPerDay.remove(r.processExecutablename);
					testTouchProcessesPerDay.put(r.processExecutablename, countt);
				}
			}
			else{
				int perHour[][]= new int[days5][24];
				int time=getTimee(r.time);
				int dayy =getDayy(r.time);

				if(time != -1){
					perHour[dayy-min5][time]=1;
					testTouchProcessesPerDay.put(r.processExecutablename, perHour);
				}
			}

		}

	}
	 */

	@SuppressWarnings("deprecation")
	private static int getTimee(String time) {
		DateFormat df = new SimpleDateFormat("h:m:s a MM/dd/yyyy");
		//System.out.println(plainTextDateTime );
		try{

			Date today = df.parse(time);            

			//int day=today.getDate();

			//System.out.println("Today = " + df.format(today));
			//System.out.println("Today = " + today.getHours());
			return today.getHours();
		} catch (Exception e)

		{
			//e.printStackTrace();
			return -1;

		}
	}


	@SuppressWarnings("deprecation")
	private static int getDayy(String time) {
		DateFormat df = new SimpleDateFormat("h:m:s a MM/dd/yyyy");
		//System.out.println(plainTextDateTime );
		try{

			Date today = df.parse(time);            

			//	int day=today.getDate();

			//System.out.println("Today = " + df.format(today));
			//System.out.println("Today = " + today.getHours());
			return today.getDate();
		} catch (Exception e)

		{
			//e.printStackTrace();
			return -1;

		}
	}

}
